package com.hsylient.javase.chapter03;

import lombok.extern.slf4j.Slf4j;
import org.junit.Test;

import java.util.HashMap;
import java.util.Hashtable;
import java.util.Map;
import java.util.Objects;

@Slf4j
public class HashMapTest {

    private static final Map<String, String> STUDENT_MAP = new HashMap<>() {
        {
            put("name", "hsylient");
            put("age", "22");
            put("weight", "27");
            put("height", "180");
        }
    };

    private static final Map<String, Integer> WALLET_BALANCE = new HashMap<>() {
        {
            put("BTC", 11);
            put("ETH", 12);
            put("USDT", 13);
        }
    };

    /**
     * 如果MAP中不存在某个KEY的操作
     */
    @Test
    public void testComputeIfAbsent() {
        String value = STUDENT_MAP.computeIfAbsent("test", String::toUpperCase);
        log.info("[computeIfAbsent测试] 存入到MAP中的test对应的value是 {}", value);
        log.info("[computeIfAbsent测试] 存入到MAP中的元素 {}", STUDENT_MAP);
    }

    /**
     * 如果MAP中存在某个KEY的操作
     */
    @Test
    public void testComputeIfPresent() {
        String name = STUDENT_MAP.computeIfPresent("name22", (x, y) -> y + 1);
        log.info("[computeIfPresent测试] KEY不在MAP中不做任何操作 {}", STUDENT_MAP);
        STUDENT_MAP.computeIfPresent("height", (key, value) -> Objects.toString(Integer.parseInt(value) - 10));
        log.info("[computeIfPresent测试] KEY存在将会操作这个KEY VALUE {}", STUDENT_MAP);
    }

    /**
     * 根据KEY获取VALUE，获取到了操作一波，旧值变新值，获取不到，把新值放进去
     */
    @Test
    public void testCompute() {
        STUDENT_MAP.compute("name", (k, v) -> k + 1);
        log.info("[compute测试] 能获取到KEY，旧值变新值 {}", STUDENT_MAP);
        STUDENT_MAP.compute("name", (k, v) -> null);
        log.info("[compute测试] 能获取到KEY,用null删除旧值 {}", STUDENT_MAP);
        STUDENT_MAP.compute("computer", (k, v) -> "COMPUTER");
        log.info("[compute测试] 不能获取到KEY，放入新值 {}", STUDENT_MAP);
        STUDENT_MAP.compute("computer", (k, v) -> null);
        log.info("[compute测试] 不能获取到KEY，放入null {}", STUDENT_MAP);
    }

    /**
     * HashMap的KV都可以为空
     * HashTable不行
     */
    @Test
    public void testOnlyAllowONeKeyNull() {
        Map<String, Integer> map = new HashMap<>();
        map.put(null, null);
        map.put(null, 13);
        System.out.println(map);
        Hashtable<Object, Object> objectObjectHashtable = new Hashtable<>();
        objectObjectHashtable.put("null", null);
        System.out.println(objectObjectHashtable);
    }


    /**
     * 如果判断不存在某个kv，将新的kv放进去。如果存在某个kv,将kv进行变动
     */
    @Test
    public void testMerge() {
        Map<String, Integer> map = new HashMap<>();
        WALLET_BALANCE.merge("BTC", 10, (key, value) -> value + 1);
        log.info(Objects.toString(WALLET_BALANCE));
    }


}
